/**
 * 项目名称（软件名称）：忠旺机械物资管理系统(mms)
 * 研发设计单位：忠旺机械设备制造有限公司机械设计院智能控制设计科设计与研发。
 * 版权所有：忠旺机械设备制造有限公司
 * 注：本项目的一切技术专利，使用规范归解释权由忠旺机械设备制造有限公司所有。
 * 软件版本：Ver 1.0.0
 * 文件路径：com.zhongwang.mms.module.purchase.service
 * 创建时间：2020年04月08日 15时52分
 **/
package com.zhongwang.mms.module.jiaGongStorage.service;

import com.zhongwang.mms.common.JsonResult;
import com.zhongwang.mms.gen.entity.AllocationOrder;
import com.zhongwang.mms.gen.entity.PInventory;
import com.zhongwang.mms.gen.entity.POrderDetail;
import com.zhongwang.mms.module.half.dao.PAllocationRecordDao;
import com.zhongwang.mms.module.jiaGongStorage.dao.StorageInDao;
import com.zhongwang.mms.module.jiaGongStorage.dao.StorageOffsetDao;
import com.zhongwang.mms.module.jiaGongStorage.model.*;
import com.zhongwang.mms.module.purchase.dao.*;
import com.zhongwang.mms.module.purchase.model.*;
import com.zhongwang.mms.module.system.log.LogService;
import com.zhongwang.mms.util.ShiroUtils;
import lombok.extern.log4j.Log4j2;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

/**
 * @ClassName： ReverseService
 * @Description：
 * @Author： 徐一贺
 * @Date： 2020/4/8 15:52
 * @Version： V1.0
 **/
@Log4j2
@Service
public class StorageOffsetService {
    @Autowired
    private PurReverseDao purReverseDao;
    @Autowired
    private PurPOrderDao purPOrderDao;
    @Autowired
    private PurPOrderDetailDao purPOrderDetailDao;
    @Autowired
    private PurPInventoryDao purPInventoryDao;
    @Autowired
    private StorageInDao storageInDao;
    @Autowired
    private LogService logService;
    @Autowired
    private PurChangeDao purChangeDao;
    @Autowired
    private StorageOffsetDao storageOffsetDao;


    /**
     * @FunctionName: findReverseList
     * @Description: 冲单页面列表查询
     * @Author: 徐一贺
     * @CreateDate: 2020/4/8 15:29
     * @Phone: 18241927380
     * @Param: [reverseQueryModel]
     * @Return: com.zhongwang.mms.common.JsonResult
     * @Version:
     */
    public List<JOffsetStorage> findReverseList(JOffsetStorage param) {
        if (param.getEndDate() != null) {
            Calendar cal = Calendar.getInstance();
            cal.setTime(param.getEndDate());
            cal.add(Calendar.DAY_OF_YEAR, 1);
            param.setEndDate(cal.getTime());
        }
        return storageOffsetDao.findReverseList(param);
    }

    /**
     * @FunctionName: reverseOrder
     * @Description: 执行冲单，检测所冲单是否是入库单，如果是入库单则验证库存数量
     * 是否足够执行对入库单冲单的操作。
     * 冲单：冲掉原数据中的明细，生成一条明细单数量为负，并和被冲记录做关联，
     * 被冲记录标识为被红冲数据，冲单数据标识为红冲数据。
     * 串料调拨单冲单时，只能冲整单，并且冲单后要更改其对应的串料申请单的执行状态。
     * 库存被拆数据不可红冲，串料、划库存 划项目
     * 如果因调整造成出入库单价、单位、物料描述发生变化，则冲回来的数据重新生成
     * 一条新的库存，新的行号与冲单明细主键关联。
     * @Author: 徐一贺
     * @CreateDate: 2020/4/9 8:43
     * @Phone: 18241927380
     * @Param: param
     * @Return: boolean
     * @Version: 1.0.0
     */
    @Transactional(rollbackFor = Exception.class)
    public JsonResult reverseOrder(JOffsetStorage param) {
        //批次处理
        if (param.getType().equals("batch")) {
            //判断是入库还是出库
            List<AllModel> AllModelList = storageOffsetDao.selectPOrderModelByOdaIds(param.getOdaIds());
            for (int i = 0; i <AllModelList.size() ; i++) {
                if (AllModelList.get(i).getOdrRedFlag() == 1) {
                    return JsonResult.fail("红冲失败！<br>失败原因：单据编号为：" + AllModelList.get(i).getOdrCode() + "。物料描述为：" + AllModelList.get(i).getOdaMatDesc() + "的身份是红冲单不可红冲！");
                }
                //如果是普通出入库单，判断是否因调整造成出入库单价、单位、物料描述发生变化，
                // 则冲回来的数据重新生成一条新的库存，新的行号与冲单明细主键关联。
                if (AllModelList.get(i).getOdrType() == 1 &&
                        AllModelList.get(i).getOdrRedFlag() == 0 &&
                        AllModelList.get(i).getOdrChangeFlag() == 0 &&
                        AllModelList.get(i).getOdrReqFlag() == 0 &&
                        AllModelList.get(i).getOdaNum() > storageOffsetDao.findInventoryByRowNumberRed(Integer.valueOf(AllModelList.get(i).getOdaId())).getItyNum()) {
                    return JsonResult.fail("红冲失败！<br>失败原因：单据编号为：" + AllModelList.get(i).getOdrCode() + "。物料描述为：" + AllModelList.get(i).getOdaMatDesc() + "的库存数量不足！");
                }
                reverseOrderOne(AllModelList.get(i));
            }

        }
        //单条处理
        else if (param.getType().equals("single")) {
            AllModel allModel = storageOffsetDao.findPOrderDetailAndPInventoryModelListByOdaId(param.getOdaIds());
            if (allModel.getOdrRedFlag() == 1) {
                return JsonResult.fail("红冲失败！<br>失败原因：单据编号为：" + allModel.getOdrCode() + "。物料描述为：" + allModel.getOdaMatDesc() + "的身份是红冲单不可红冲！");
            }
            //如果是普通出入库单，判断是否因调整造成出入库单价、单位、物料描述发生变化，
            // 则冲回来的数据重新生成一条新的库存，新的行号与冲单明细主键关联。
            if (allModel.getOdrType() == 1 &&
                    allModel.getOdrRedFlag() == 0 &&
                    allModel.getOdrChangeFlag() == 0 &&
                    allModel.getOdrReqFlag() == 0 &&
                    allModel.getOdaNum() > storageOffsetDao.findInventoryByRowNumberRed(Integer.valueOf(param.getOdaIds())).getItyNum()) {
                return JsonResult.fail("红冲失败！<br>失败原因：单据编号为：" + allModel.getOdrCode() + "。物料描述为：" + allModel.getOdaMatDesc() + "的库存数量不足！");
            }
            reverseOrderOne(allModel);
        }
        return JsonResult.success();
    }
    public  void   reverseOrderOne(AllModel allModel){
        if (allModel.getOdrType() == 1 &&
                allModel.getOdrRedFlag() == 0 &&
                allModel.getOdrChangeFlag() == 0 &&
                allModel.getOdrReqFlag() == 0 &&
                allModel.getOdaNum() <= storageOffsetDao.findInventoryByRowNumber(allModel.getOdaId()).getItyNum()
                ) {
            //冲入库单
            JStorageDetail jStorageDetail = storageOffsetDao.findOrderDetailByOdaId(allModel.getOdaId());
            //执行红冲单据明细
            jStorageDetail.setOdaRedFlag(1);
            jStorageDetail.setOdaRedDate(new Date());
            jStorageDetail.setOdaRedUserId(ShiroUtils.getUser().getId());
            Integer odaId = jStorageDetail.getOdaId();
            //标记被红冲数据
            storageOffsetDao.updateByPrimaryKeySelective(jStorageDetail);
            Double redNum = 0 - jStorageDetail.getOdaNum();
            jStorageDetail.setOdaNum(redNum);
            jStorageDetail.setOdaRushId(jStorageDetail.getOdaId());
            jStorageDetail.setOdaRedFlag(2);
            jStorageDetail.setOdaRedDate(new Date());
            jStorageDetail.setOdaRedUserId(ShiroUtils.getUser().getId());
            //标记红冲数据
            storageInDao.insertTStorageDetail(jStorageDetail);
            //根据单据类型对库存操作
            JStorageInventory jStorageInventory = storageOffsetDao.findInventoryByRowNumber(odaId);
            if (jStorageDetail.getOdaType() == 1) {
                //如果是出库则增加库存
                jStorageInventory.setItyNum(jStorageInventory.getItyNum() - Math.abs(redNum));
                jStorageInventory.setItyAvaNum(jStorageInventory.getItyNum());
            }
            //执行对库存操作
            storageOffsetDao.updateNumByPrimaryKey(jStorageInventory);
            logService.saveLog("红冲", "被红冲单号：" + allModel.getOdrCode() + ";被红冲物料名称：" + jStorageDetail.getOdaMatDesc() + ";单据类型：入库单");
        }
        //如果是出库单直接入库即可
        else if (allModel.getOdrType() == 2 &&
                allModel.getOdrRedFlag() == 0 &&
                allModel.getOdrChangeFlag() == 0 &&
                allModel.getOdrReqFlag() == 0
                ) {
            //冲出库单
            JStorageDetail jStorageDetail = storageOffsetDao.findOrderDetailByOdaId(allModel.getOdaId());
            //执行红冲单据明细
            jStorageDetail.setOdaRedFlag(1);
            jStorageDetail.setOdaRedDate(new Date());
            jStorageDetail.setOdaRedUserId(ShiroUtils.getUser().getId());
            Integer odaId = jStorageDetail.getOdaId();
            //标记被红冲数据
            storageOffsetDao.updateByPrimaryKeySelective(jStorageDetail);
            Double redNum = 0 - jStorageDetail.getOdaNum();
            jStorageDetail.setOdaNum(redNum);
            jStorageDetail.setOdaRushId(jStorageDetail.getOdaId());
            jStorageDetail.setOdaRedFlag(2);
            jStorageDetail.setOdaRedDate(new Date());
            jStorageDetail.setOdaRedUserId(ShiroUtils.getUser().getId());
            //标记红冲数据
            storageInDao.insertTStorageDetail(jStorageDetail);
            //根据单据类型对库存操作
            JStorageInventory jStorageInventory = storageOffsetDao.findInventoryByodaOutItyId(odaId);
            if (jStorageDetail.getOdaType() == 2) {
                //如果是出库则增加库存
                jStorageInventory.setItyNum(jStorageInventory.getItyNum() + Math.abs(redNum));
                jStorageInventory.setItyAvaNum(jStorageInventory.getItyNum());
            }
            //执行对库存操作
            storageOffsetDao.updateNumByPrimaryKey(jStorageInventory);
            logService.saveLog("红冲", "被红冲单号：" + allModel.getOdrCode() + ";被红冲物料名称：" + jStorageDetail.getOdaMatDesc() + ";单据类型：出库单");
        }
    }

}